வலுவான, பிழை இல்லாத குறியீட்டை எழுத TypeScript, வேறுபடுத்தப்பட்ட யூனியன்கள் மற்றும் நவீன லைப்ரரிகளைப் பயன்படுத்தி JavaScript இல் வகை-பாதுகாப்பான, தொகுப்பு-நேர சரிபார்க்கப்பட்ட பேட்டர்ன் பொருத்துதலை எப்படி அடைவது என்பதை ஆராயுங்கள்.
JavaScript பேட்டர்ன் பொருத்துதல் & வகை பாதுகாப்பு: தொகுப்பு-நேர சரிபார்ப்புக்கான ஒரு வழிகாட்டி
பேட்டர்ன் பொருத்துதல் என்பது நவீன நிரலாக்கத்தில் மிகவும் சக்திவாய்ந்த மற்றும் வெளிப்படையான அம்சங்களில் ஒன்றாகும், இது ஹாஸ்கெல், ரஸ்ட் மற்றும் எஃப்# போன்ற செயல்பாட்டு மொழிகளில் நீண்ட காலமாக கொண்டாடப்படுகிறது. இது டெவலப்பர்கள் தரவை கட்டமைக்க மற்றும் சுருக்கமாகவும் நம்பமுடியாத அளவிற்கு படிக்கக்கூடியதாகவும் இருக்கும் வகையில் அதன் கட்டமைப்பின் அடிப்படையில் குறியீட்டை இயக்க அனுமதிக்கிறது. JavaScript தொடர்ந்து வளர்ச்சியடைந்து வருவதால், டெவலப்பர்கள் இந்த சக்திவாய்ந்த முன்னுதாரணங்களை ஏற்றுக்கொள்வதில் அதிக ஆர்வம் காட்டுகின்றனர். இருப்பினும், ஒரு முக்கியமான சவால் உள்ளது: JavaScript இன் மாறும் உலகில் இந்த மொழிகளின் வலுவான வகை பாதுகாப்பு மற்றும் தொகுப்பு-நேர உத்தரவாதங்களை நாம் எப்படி அடைவது?
TypeScript இன் நிலையான வகை அமைப்பைப் பயன்படுத்துவதில் பதில் உள்ளது. JavaScript தானாகவே சொந்த பேட்டர்ன் பொருத்துதலை நோக்கி நகரும்போது, அதன் மாறும் தன்மை எந்தவொரு சோதனையும் இயக்க நேரத்தில் நிகழும் என்று அர்த்தம், இது உற்பத்தியில் எதிர்பாராத பிழைகளுக்கு வழிவகுக்கும். இந்த கட்டுரை உண்மையான தொகுப்பு-நேர முறை சரிபார்ப்பை இயக்கும் நுட்பங்கள் மற்றும் கருவிகளைப் பற்றிய ஆழமான புரிதலை வழங்குகிறது, உங்கள் பயனர்கள் கண்டறிவதற்கு முன்பு, நீங்கள் தட்டச்சு செய்யும்போதே பிழைகளை நீங்கள் பிடிப்பதை உறுதி செய்கிறது.
TypeScript இன் சக்திவாய்ந்த அம்சங்களை பேட்டர்ன் பொருத்துதலின் நேர்த்தியுடன் இணைத்து வலுவான, சுய-ஆவணப்படுத்தப்பட்ட மற்றும் பிழை-எதிர்ப்பு அமைப்புகளை எவ்வாறு உருவாக்குவது என்பதை ஆராய்வோம். இயக்க நேர பிழைகளின் முழு வகுப்பையும் அகற்றவும், பாதுகாப்பான மற்றும் பராமரிக்க எளிதான குறியீட்டை எழுதவும் தயாராகுங்கள்.
பேட்டர்ன் பொருத்துதல் என்றால் என்ன?
அதன் மையத்தில், பேட்டர்ன் பொருத்துதல் என்பது ஒரு அதிநவீன கட்டுப்பாட்டு ஓட்ட பொறிமுறையாகும். இது ஒரு சூப்பர்-பவர் `switch` கூற்றைப் போன்றது. எண்கள் அல்லது சரங்கள் போன்ற எளிய மதிப்புகளுக்கு எதிராக சமத்துவத்தை சரிபார்ப்பதற்கு பதிலாக, பேட்டர்ன் பொருத்துதல் ஒரு மதிப்பை சிக்கலான 'பேட்டர்ன்களுக்கு' எதிராக சரிபார்க்கவும், ஒரு பொருத்தம் காணப்பட்டால், அந்த மதிப்பின் பகுதிகளுக்கு மாறிகளைப் பிணைக்கவும் உங்களை அனுமதிக்கிறது.
பாரம்பரிய அணுகுமுறைகளுடன் ஒப்பிட்டுப் பார்ப்போம்:
பழைய வழி: `if-else` சங்கிலிகள் மற்றும் `switch`
ஒரு வடிவியல் வடிவத்தின் பரப்பளவைக் கணக்கிடும் ஒரு செயல்பாட்டைக் கவனியுங்கள். ஒரு பாரம்பரிய அணுகுமுறையுடன், உங்கள் குறியீடு இப்படி இருக்கலாம்:
// Shape is an object with a 'type' property
function calculateArea(shape) {
if (shape.type === 'circle') {
return Math.PI * shape.radius * shape.radius;
} else if (shape.type === 'square') {
return shape.sideLength * shape.sideLength;
} else if (shape.type === 'rectangle') {
return shape.width * shape.height;
} else {
throw new Error('Unsupported shape type');
}
}
இது வேலை செய்கிறது, ஆனால் இது சொற்பொழிவும் பிழைக்கு வாய்ப்புள்ளது. நீங்கள் ஒரு புதிய வடிவத்தை, ஒரு `triangle` ஐச் சேர்த்தால், ஆனால் இந்த செயல்பாட்டைப் புதுப்பிக்க மறந்துவிட்டால் என்ன செய்வது? குறியீடு இயக்க நேரத்தில் ஒரு பொதுவான பிழையை எறியும், இது உண்மையான பிழை அறிமுகப்படுத்தப்பட்ட இடத்திலிருந்து வெகு தொலைவில் இருக்கலாம்.
பேட்டர்ன் பொருத்துதல் வழி: அறிவிப்பு மற்றும் வெளிப்படையானது
பேட்டர்ன் பொருத்துதல் இந்த தர்க்கத்தை மிகவும் அறிவிப்புடன் மாற்றுகிறது. கட்டாய சோதனைகளின் தொடருக்கு பதிலாக, நீங்கள் எதிர்பார்க்கும் பேட்டர்ன்களை அறிவித்து, எடுக்க வேண்டிய செயல்களை அறிவிக்கவும்:
// Pseudocode for a future JavaScript pattern matching feature
function calculateArea(shape) {
match (shape) {
when ({ type: 'circle', radius }): return Math.PI * radius * radius;
when ({ type: 'square', sideLength }): return sideLength * sideLength;
when ({ type: 'rectangle', width, height }): return width * height;
default: throw new Error('Unsupported shape type');
}
}
முக்கிய நன்மைகள் உடனடியாகத் தெரிகிறது:
- கட்டமைப்பை அழித்தல்: `radius`, `width` மற்றும் `height` போன்ற மதிப்புகள் `shape` பொருளிலிருந்து தானாகவே பிரித்தெடுக்கப்படுகின்றன.
- படிக்கக்கூடிய தன்மை: குறியீட்டின் நோக்கம் தெளிவாக உள்ளது. ஒவ்வொரு `when` பிரிவும் ஒரு குறிப்பிட்ட தரவு கட்டமைப்பையும் அதன் தொடர்புடைய தர்க்கத்தையும் விவரிக்கிறது.
- முழுமை: வகை பாதுகாப்பிற்கான மிக முக்கியமான நன்மை இதுதான். ஒரு உண்மையான வலுவான பேட்டர்ன் பொருத்துதல் அமைப்பு சாத்தியமான ஒரு நிகழ்வைக் கையாள மறந்துவிட்டால் தொகுப்பு நேரத்தில் உங்களை எச்சரிக்க முடியும். இதுவே எங்கள் முதன்மை குறிக்கோள்.
JavaScript சவால்: ஆற்றல் எதிராக பாதுகாப்பு
JavaScript இன் மிகப்பெரிய பலம் - அதன் நெகிழ்வுத்தன்மை மற்றும் மாறும் தன்மை - வகை பாதுகாப்பைப் பொறுத்தவரை அதன் மிகப்பெரிய பலவீனமாகும். தொகுப்பு நேரத்தில் ஒப்பந்தங்களைச் செயல்படுத்தும் நிலையான வகை அமைப்பு இல்லாமல், எளிய JavaScript இல் பேட்டர்ன் பொருத்துதல் இயக்க நேர சோதனைகளுக்கு மட்டுப்படுத்தப்பட்டுள்ளது. இதன் பொருள்:
- தொகுப்பு-நேர உத்தரவாதங்கள் இல்லை: உங்கள் குறியீடு இயங்கும் வரை மற்றும் அந்த குறிப்பிட்ட பாதையைத் தாக்கும் வரை நீங்கள் ஒரு நிகழ்வைத் தவறவிட்டீர்கள் என்பது உங்களுக்குத் தெரியாது.
- அமைதியான தோல்விகள்: நீங்கள் ஒரு இயல்புநிலை நிகழ்வை மறந்துவிட்டால், பொருந்தாத மதிப்பு வெறுமனே `undefined` ஆக இருக்கலாம், இது கீழ்தோன்றல் பிழைகளை ஏற்படுத்தும்.
- மறுசீரமைப்பு கனவுகள்: ஒரு தரவு கட்டமைப்பில் ஒரு புதிய மாறுபாட்டைச் சேர்ப்பது (எ.கா., ஒரு புதிய நிகழ்வு வகை, ஒரு புதிய API பதில் நிலை) அதைக் கையாள வேண்டிய அனைத்து இடங்களையும் கண்டுபிடிக்க ஒரு உலகளாவிய தேடல் மற்றும் மாற்றீடு தேவைப்படுகிறது. ஒன்றை தவறவிட்டால் உங்கள் விண்ணப்பத்தை உடைக்க முடியும்.
இங்கேதான் TypeScript விளையாட்டை முழுவதுமாக மாற்றுகிறது. அதன் நிலையான வகை அமைப்பு எங்கள் தரவை துல்லியமாக மாதிரியாகவும், ஒவ்வொரு சாத்தியமான மாறுபாட்டையும் நாங்கள் கையாளுகிறோம் என்பதை உறுதிப்படுத்த கம்பைலரைப் பயன்படுத்தவும் அனுமதிக்கிறது. எப்படி என்று ஆராய்வோம்.
தொழில்நுட்பம் 1: வேறுபடுத்தப்பட்ட யூனியன்களுடன் கூடிய அடித்தளம்
வகை-பாதுகாப்பான பேட்டர்ன் பொருத்துதலை இயக்குவதற்கான ஒற்றை மிக முக்கியமான TypeScript அம்சம் வேறுபடுத்தப்பட்ட யூனியன் (டேக் செய்யப்பட்ட யூனியன் அல்லது இயற்கணித தரவு வகை என்றும் அழைக்கப்படுகிறது). இது பல தனித்துவமான சாத்தியக்கூறுகளில் ஒன்றாக இருக்கக்கூடிய ஒரு வகையை மாதிரியாகக் கொள்வதற்கான சக்திவாய்ந்த வழியாகும்.
வேறுபடுத்தப்பட்ட யூனியன் என்றால் என்ன?
வேறுபடுத்தப்பட்ட யூனியன் மூன்று கூறுகளிலிருந்து கட்டமைக்கப்பட்டுள்ளது:
- தனித்துவமான வகைகளின் தொகுப்பு (யூனியன் உறுப்பினர்கள்).
- ஒரு லிட்டரல் வகையுடன் கூடிய பொதுவான சொத்து, வேறுபடுத்தி அல்லது டேக் என்று அழைக்கப்படுகிறது. யூனியனில் உள்ள குறிப்பிட்ட வகையை சுருக்க இந்த சொத்து TypeScript ஐ அனுமதிக்கிறது.
- அனைத்து உறுப்பினர் வகைகளையும் இணைக்கும் யூனியன் வகை.
இந்த பேட்டர்னைப் பயன்படுத்தி எங்கள் வடிவ உதாரணத்தை மறுவடிவமைப்போம்:
// 1. Define the distinct member types
interface Circle {
kind: 'circle'; // The discriminant
radius: number;
}
interface Square {
kind: 'square'; // The discriminant
sideLength: number;
}
interface Rectangle {
kind: 'rectangle'; // The discriminant
width: number;
height: number;
}
// 2. Create the union type
type Shape = Circle | Square | Rectangle;
இப்போது, `Shape` வகையின் ஒரு மாறி இந்த மூன்று இடைமுகங்களில் ஒன்றாக இருக்க வேண்டும். `kind` சொத்து TypeScript இன் வகை குறுகும் திறன்களைத் திறக்கும் திறவுகோலாக செயல்படுகிறது.
தொகுப்பு-நேர முழுமை சரிபார்ப்பை செயல்படுத்துதல்
எங்கள் வேறுபடுத்தப்பட்ட யூனியன் இடத்தில் இருப்பதால், ஒவ்வொரு சாத்தியமான வடிவத்தையும் கையாள கம்பைலரால் உத்தரவாதம் அளிக்கப்படும் ஒரு செயல்பாட்டை இப்போது எழுதலாம். மாய மூலப்பொருள் TypeScript இன் `never` வகை, இது ஒருபோதும் நடக்கக்கூடாது என்று ஒரு மதிப்பைக் குறிக்கிறது.
இதைச் செயல்படுத்த ஒரு எளிய உதவி செயல்பாட்டை எழுதலாம்:
function assertUnreachable(x: never): never {
throw new Error("Didn't expect to get here");
}
இப்போது, எங்கள் `calculateArea` செயல்பாட்டை ஒரு நிலையான `switch` அறிக்கையைப் பயன்படுத்தி மீண்டும் எழுதுவோம். `default` விஷயத்தில் என்ன நடக்கிறது என்று பாருங்கள்:
function calculateArea(shape: Shape): number {
switch (shape.kind) {
case 'circle':
// TypeScript knows `shape` is a Circle here!
return Math.PI * shape.radius ** 2;
case 'square':
// TypeScript knows `shape` is a Square here!
return shape.sideLength ** 2;
case 'rectangle':
// TypeScript knows `shape` is a Rectangle here!
return shape.width * shape.height;
default:
// If we've handled all cases, `shape` will be of type `never`
return assertUnreachable(shape);
}
}
இந்த குறியீடு சரியாக தொகுக்கிறது. ஒவ்வொரு `case` தொகுதிக்குள்ளும், TypeScript `shape` வகையை `Circle`, `Square` அல்லது `Rectangle` ஆகக் குறைத்துள்ளது, இது `radius` போன்ற பண்புகளைப் பாதுகாப்பாக அணுக அனுமதிக்கிறது.
இப்போது மாய தருணத்திற்கு. எங்கள் கணினியில் ஒரு புதிய வடிவத்தை அறிமுகப்படுத்துவோம்:
interface Triangle {
kind: 'triangle';
base: number;
height: number;
}
type Shape = Circle | Square | Rectangle | Triangle; // Add it to the union
நாங்கள் `Triangle` ஐ `Shape` யூனியனில் சேர்த்தவுடன், எங்கள் `calculateArea` செயல்பாடு உடனடியாக ஒரு தொகுப்பு-நேர பிழையை உருவாக்கும்:
// In the `default` block of `calculateArea`:
return assertUnreachable(shape);
// ~~~~~
// Argument of type 'Triangle' is not assignable to parameter of type 'never'.
இந்த பிழை நம்பமுடியாத அளவிற்கு மதிப்புமிக்கது. TypeScript கம்பைலர் எங்களிடம் கூறுகிறது, "சாத்தியமான ஒவ்வொரு `Shape` ஐயும் கையாள நீங்கள் உறுதியளித்தீர்கள், ஆனால் நீங்கள் `Triangle` ஐப் பற்றி மறந்துவிட்டீர்கள். `shape` மாறி இயல்புநிலை வழக்கில் இன்னும் ஒரு `Triangle` ஆக இருக்கலாம், அது `never` க்கு ஒதுக்க முடியாது."
பிழையை சரிசெய்ய, காணாமல் போன நிகழ்வைச் சேர்க்கிறோம். கம்பைலர் எங்கள் பாதுகாப்பு வலையாக மாறும், எங்கள் தர்க்கம் எங்கள் தரவு மாதிரியுடன் ஒத்திசைவாக இருப்பதை உறுதி செய்கிறது.
// ... inside the switch
case 'triangle':
return 0.5 * shape.base * shape.height;
default:
return assertUnreachable(shape);
// ... now the code compiles again!
இந்த அணுகுமுறையின் நன்மை தீமைகள்
- நன்மைகள்:
- பூஜ்ஜிய சார்புகள்: இது முக்கிய TypeScript அம்சங்களை மட்டுமே பயன்படுத்துகிறது.
- அதிகபட்ச வகை பாதுகாப்பு: இரும்புக்கவசம் தொகுப்பு-நேர உத்தரவாதங்களை வழங்குகிறது.
- சிறந்த செயல்திறன்: இது மிகவும் உகந்த நிலையான JavaScript `switch` அறிக்கைக்கு தொகுக்கிறது.
- குறைகள்:
- சொற்பொழிவு: `switch`, `case`, `break`/`return` மற்றும் `default` கொதிகலன் கடினமானதாக உணர முடியும்.
- ஒரு வெளிப்பாடு அல்ல: ஒரு `switch` அறிக்கையை நேரடியாக திருப்பித் தரவோ அல்லது ஒரு மாறிக்கு ஒதுக்கவோ முடியாது, இது அதிக கட்டாய குறியீடு பாணிகளுக்கு வழிவகுக்கிறது.
தொழில்நுட்பம் 2: நவீன லைப்ரரிகளுடன் எர்கோனமிக் APIகள்
`switch` அறிக்கையுடன் வேறுபடுத்தப்பட்ட யூனியன் அடித்தளமாக இருந்தாலும், அதன் கொதிகலன் சலிப்பை ஏற்படுத்தும். இது TypeScript இன் கம்பைலரை பாதுகாப்பிற்காகப் பயன்படுத்தும் போது, பேட்டர்ன் பொருத்துதலுக்கு மிகவும் செயல்பாட்டு, வெளிப்படையான மற்றும் எர்கோனமிக் API ஐ வழங்கும் அற்புதமான திறந்த மூல லைப்ரரிகளின் வளர்ச்சிக்கு வழிவகுத்தது.
`ts-pattern` அறிமுகம்
இந்த இடத்தில் மிகவும் பிரபலமான மற்றும் சக்திவாய்ந்த லைப்ரரிகளில் ஒன்று `ts-pattern`. இது `switch` அறிக்கைகளை ஒரு சரளமான, சங்கிலி API உடன் மாற்ற அனுமதிக்கிறது, இது ஒரு வெளிப்பாடாக வேலை செய்கிறது.
`ts-pattern` ஐப் பயன்படுத்தி எங்கள் `calculateArea` செயல்பாட்டை மீண்டும் எழுதுவோம்:
import { match } from 'ts-pattern';
function calculateAreaWithTsPattern(shape: Shape): number {
return match(shape)
.with({ kind: 'circle' }, (s) => Math.PI * s.radius ** 2)
.with({ kind: 'square' }, (s) => s.sideLength ** 2)
.with({ kind: 'rectangle' }, (s) => s.width * s.height)
.with({ kind: 'triangle' }, (s) => 0.5 * s.base * s.height)
.exhaustive(); // This is the key to compile-time safety
}
என்ன நடக்கிறது என்பதை உடைப்போம்:
- `match(shape)`: இது பொருந்த வேண்டிய மதிப்பைக் கொண்டு, பேட்டர்ன் பொருத்துதல் வெளிப்பாட்டைத் தொடங்குகிறது.
- `.with({ kind: '...' }, handler)`: ஒவ்வொரு `.with()` அழைப்பும் ஒரு பேட்டர்னை வரையறுக்கிறது. இரண்டாவது வாதத்தின் வகையை (`handler` செயல்பாடு) ஊகிக்க `ts-pattern` போதுமானதாக உள்ளது. `{ kind: 'circle' }` பேட்டர்னுக்கு, கையாளுபவருக்கான உள்ளீடு `s` `Circle` வகையாக இருக்கும் என்று அது அறிந்துள்ளது.
- `.exhaustive()`: இந்த முறை எங்கள் `assertUnreachable` தந்திரத்திற்கு சமம். சாத்தியமான அனைத்து நிகழ்வுகளையும் கையாள வேண்டும் என்று `ts-pattern` க்கு இது கூறுகிறது. நாங்கள் `.with({ kind: 'triangle' }, ...)` வரியை அகற்றினால், `ts-pattern` `.exhaustive()` அழைப்பில் தொகுப்பு-நேர பிழையைத் தூண்டும், போட்டி முழுமையானது அல்ல என்று எங்களிடம் கூறுகிறது.
`ts-pattern` இன் மேம்பட்ட அம்சங்கள்
`ts-pattern` எளிய சொத்து பொருத்துதலுக்கு அப்பால் செல்கிறது:
- `.when()` உடன் முன்னறிவிப்பு பொருத்துதல்: ஒரு நிபந்தனையின் அடிப்படையில் பொருத்தவும்.
match(input) .when(isString, (str) => `It's a string: ${str}`) .when(isNumber, (num) => `It's a number: ${num}`) .otherwise(() => 'It is something else'); - ஆழமாக கூடு கட்டப்பட்ட பேட்டர்ன்கள்: சிக்கலான பொருள் கட்டமைப்புகளில் பொருத்தவும்.
match(user) .with({ address: { city: 'Paris' } }, () => 'User is in Paris') .otherwise(() => 'User is elsewhere'); - வைல்ட் கார்டுகள் மற்றும் சிறப்பு தேர்வாளர்கள்: ஒரு பேட்டர்னில் ஒரு மதிப்பைப் பிடிக்க `P.select()` ஐப் பயன்படுத்தவும் அல்லது ஒரு குறிப்பிட்ட வகையின் எந்த மதிப்பையும் பொருத்த `P.string`, `P.number` ஐப் பயன்படுத்தவும்.
import { match, P } from 'ts-pattern'; match(event) .with({ type: 'USER_LOGIN', user: { name: P.select() } }, (name) => { console.log(`${name} logged in.`); }) .otherwise(() => {});
`ts-pattern` போன்ற ஒரு லைப்ரரியைப் பயன்படுத்துவதன் மூலம், நீங்கள் இரண்டு உலகங்களின் சிறந்ததைப் பெறுவீர்கள்: TypeScript இன் `never` சரிபார்ப்பின் வலுவான தொகுப்பு-நேர பாதுகாப்பு, ஒரு சுத்தமான, அறிவிப்பு மற்றும் அதிக வெளிப்படையான API உடன் இணைக்கப்பட்டுள்ளது.
எதிர்காலம்: TC39 பேட்டர்ன் பொருத்துதல் முன்மொழிவு
JavaScript மொழி சொந்த பேட்டர்ன் பொருத்துதலுக்கு வரும் பாதையில் உள்ளது. மொழியில் `match` வெளிப்பாட்டைச் சேர்க்க TC39 (JavaScript ஐ தரப்படுத்திய குழு) இல் ஒரு செயலில் முன்மொழிவு உள்ளது.
முன்மொழியப்பட்ட தொடரியல்
தொடரியல் இப்படி இருக்கலாம்:
// This is proposed JavaScript syntax and might change
const getMessage = (response) => {
return match (response) {
when ({ status: 200, body: b }) { return `Success with body: ${b}`; }
when ({ status: 404 }) { return 'Not Found'; }
when ({ status: s if s >= 500 }) { return `Server Error: ${s}`; }
default { return 'Unknown response'; }
}
};
வகை பாதுகாப்பு பற்றி என்ன?
இது எங்கள் விவாதத்திற்கான முக்கியமான கேள்வி. தனியாக, ஒரு சொந்த JavaScript பேட்டர்ன் பொருத்துதல் அம்சம் அதன் சோதனைகளை இயக்க நேரத்தில் செய்யும். இது உங்கள் TypeScript வகைகளைப் பற்றி அறியாது.
இருப்பினும், இந்த புதிய தொடரியலின் மேல் TypeScript குழு நிலையான பகுப்பாய்வை உருவாக்கும் என்பது கிட்டத்தட்ட உறுதியாகிவிட்டது. வகை குறுகலைச் செய்ய TypeScript `if` அறிக்கைகள் மற்றும் `switch` தொகுதிகளைப் பகுப்பாய்வு செய்வது போலவே, அது `match` வெளிப்பாடுகளைப் பகுப்பாய்வு செய்யும். இதன் பொருள் இறுதியில் சிறந்த முடிவைப் பெற முடியும்:
- சொந்த, செயல்திறன் தொடரியல்: லைப்ரரிகள் அல்லது டிரான்ஸ்பிலேஷன் தந்திரங்கள் தேவையில்லை.
- முழு தொகுப்பு-நேர பாதுகாப்பு: இன்று `switch` க்குச் செய்வது போலவே, TypeScript `match` வெளிப்பாட்டை வேறுபடுத்தப்பட்ட யூனியனுக்கு எதிராக முழுமைக்காகச் சரிபார்க்கும்.
இந்த அம்சம் முன்மொழிவு நிலைகள் வழியாகவும், உலாவிகள் மற்றும் இயக்க நேரங்களிலும் வருவதற்கு நாங்கள் காத்திருக்கும்போது, வேறுபடுத்தப்பட்ட யூனியன்கள் மற்றும் லைப்ரரிகளுடன் இன்று நாம் விவாதித்த நுட்பங்கள் உற்பத்திக்கு தயாரான, அதிநவீன தீர்வாகும்.
நடைமுறை பயன்பாடுகள் மற்றும் சிறந்த நடைமுறைகள்
இந்த பேட்டர்ன்கள் பொதுவான, நிஜ உலக வளர்ச்சி காட்சிகளுக்கு எவ்வாறு பொருந்தும் என்று பார்ப்போம்.
நிலை மேலாண்மை (Redux, Zustand, etc.)
செயல்களுடன் நிலையை நிர்வகிப்பது வேறுபடுத்தப்பட்ட யூனியன்களுக்கான சரியான பயன்பாட்டு வழக்கு. செயல் வகைகளுக்கு சரக் மாறிலிகளைப் பயன்படுத்துவதற்குப் பதிலாக, சாத்தியமான அனைத்து செயல்களுக்கும் வேறுபடுத்தப்பட்ட யூனியனை வரையறுக்கவும்.
// Define actions
interface IncrementAction { type: 'counter/increment'; payload: number; }
interface DecrementAction { type: 'counter/decrement'; payload: number; }
interface ResetAction { type: 'counter/reset'; }
type CounterAction = IncrementAction | DecrementAction | ResetAction;
// A type-safe reducer
function counterReducer(state: number, action: CounterAction): number {
return match(action)
.with({ type: 'counter/increment' }, (act) => state + act.payload)
.with({ type: 'counter/decrement' }, (act) => state - act.payload)
.with({ type: 'counter/reset' }, () => 0)
.exhaustive();
}
இப்போது, நீங்கள் `CounterAction` யூனியனில் ஒரு புதிய செயலைச் சேர்த்தால், TypeScript குறைப்பானை புதுப்பிக்க உங்களை கட்டாயப்படுத்தும். மேலும் மறக்கப்பட்ட செயல் கையாளுபவர்கள் இல்லை!
API பதில்களைக் கையாளுதல்
ஒரு API இலிருந்து தரவைப் பெறுவதில் பல நிலைகள் உள்ளன: ஏற்றுதல், வெற்றி மற்றும் பிழை. வேறுபடுத்தப்பட்ட யூனியனுடன் இதை வடிவமைப்பது உங்கள் UI தர்க்கத்தை மிகவும் வலுவானதாக ஆக்குகிறது.
// Model the async data state
type RemoteData =
| { status: 'idle' }
| { status: 'loading' }
| { status: 'success'; data: T }
| { status: 'error'; error: E };
// In your UI component (e.g., React)
function UserProfile({ userId }: { userId: string }) {
const [userState, setUserState] = useState>({ status: 'idle' });
// ... useEffect to fetch data and update state ...
return match(userState)
.with({ status: 'idle' }, () => Click a button to load the user.
)
.with({ status: 'loading' }, () => )
.with({ status: 'success' }, (state) => )
.with({ status: 'error' }, (state) => )
.exhaustive();
}
உங்கள் தரவு மீட்டெடுப்பின் ஒவ்வொரு சாத்தியமான நிலைக்கும் ஒரு UI ஐ செயல்படுத்தியுள்ளீர்கள் என்பதை இந்த அணுகுமுறை உத்தரவாதம் செய்கிறது. ஏற்றுதல் அல்லது பிழை நிகழ்வைக் கையாள நீங்கள் தற்செயலாக மறந்துவிட முடியாது.
சிறந்த நடைமுறைகள் சுருக்கம்
- வேறுபடுத்தப்பட்ட யூனியன்களுடன் மாதிரி: உங்களுக்கு பல தனித்துவமான வடிவங்களில் ஒன்றாக இருக்கக்கூடிய மதிப்பு இருக்கும்போது, வேறுபடுத்தப்பட்ட யூனியனைப் பயன்படுத்தவும். TypeScript இல் வகை-பாதுகாப்பான பேட்டர்ன்களின் அடித்தளம் இது.
- எப்போதும் முழுமையைச் செயல்படுத்தவும்: நீங்கள் ஒரு `switch` அறிக்கையுடன் `never` தந்திரத்தைப் பயன்படுத்தினாலும் அல்லது ஒரு லைப்ரரியின் `.exhaustive()` முறையைப் பயன்படுத்தினாலும், பேட்டர்ன் போட்டியை ஒருபோதும் திறந்ததாக விடாதீர்கள். இங்கிருந்துதான் பாதுகாப்பு வருகிறது.
- சரியான கருவியைத் தேர்வுசெய்க: எளிய நிகழ்வுகளுக்கு, ஒரு `switch` அறிக்கை சரியானது. சிக்கலான தர்க்கம், கூடு கட்டப்பட்ட பொருத்துதல் அல்லது மிகவும் செயல்பாட்டு பாணிக்கு, `ts-pattern` போன்ற ஒரு லைப்ரரி படிக்கக்கூடிய தன்மையை கணிசமாக மேம்படுத்தும் மற்றும் கொதிகலனைக் குறைக்கும்.
- பேட்டர்ன்களைப் படிக்கக்கூடியதாக வைத்திருங்கள்: குறிக்கோள் தெளிவு. ஒரு பார்வையில் புரிந்துகொள்வது கடினமான அதிக சிக்கலான, கூடு கட்டப்பட்ட பேட்டர்ன்களைத் தவிர்க்கவும். சில நேரங்களில், ஒரு போட்டியை சிறிய செயல்பாடுகளாக உடைப்பது ஒரு சிறந்த அணுகுமுறையாகும்.
முடிவு: பாதுகாப்பான JavaScript இன் எதிர்காலத்தை எழுதுதல்
பேட்டர்ன் பொருத்துதல் என்பது ஒரு தொடரியல் இனிப்பை விட அதிகம்; இது மிகவும் அறிவிப்பு, படிக்கக்கூடிய மற்றும் - மிக முக்கியமாக - மிகவும் வலுவான குறியீட்டிற்கு வழிவகுக்கும் ஒரு முன்னுதாரணமாகும். JavaScript இல் அதன் சொந்த வருகைக்காக நாங்கள் ஆவலுடன் காத்திருக்கும்போது, அதன் நன்மைகளைப் பெற நாங்கள் காத்திருக்க வேண்டியதில்லை.
TypeScript இன் நிலையான வகை அமைப்பின் சக்தியைப் பயன்படுத்துவதன் மூலம், குறிப்பாக வேறுபடுத்தப்பட்ட யூனியன்களுடன், தொகுப்பு நேரத்தில் சரிபார்க்கக்கூடிய அமைப்புகளை உருவாக்கலாம். இந்த அணுகுமுறை பிழை கண்டறிதலை இயக்க நேரத்தில் இருந்து வளர்ச்சி நேரத்திற்கு மாற்றுகிறது, இது எண்ணற்ற மணிநேர பிழைகளை நீக்குகிறது மற்றும் உற்பத்தி சம்பவங்களைத் தடுக்கிறது. `ts-pattern` போன்ற லைப்ரரிகள் இந்த உறுதியான அடித்தளத்தின் மீது உருவாக்கப்படுகின்றன, வகை-பாதுகாப்பான குறியீட்டை எழுதுவதை ஒரு மகிழ்ச்சியாக மாற்றும் ஒரு நேர்த்தியான மற்றும் சக்திவாய்ந்த API ஐ வழங்குகின்றன.
தொகுப்பு-நேர பேட்டர்ன் சரிபார்ப்பை ஏற்றுக்கொள்வது மிகவும் மீள்தன்மை மற்றும் பராமரிக்கக்கூடிய பயன்பாடுகளை எழுதுவதற்கான ஒரு படியாகும். இது உங்கள் தரவு இருக்கக்கூடிய அனைத்து சாத்தியமான நிலைகளைப் பற்றி வெளிப்படையாக சிந்திக்க உங்களை ஊக்குவிக்கிறது, தெளிவின்மையை நீக்குகிறது மற்றும் உங்கள் குறியீட்டின் தர்க்கத்தை படிக தெளிவாக்குகிறது. இன்று வேறுபடுத்தப்பட்ட யூனியன்களுடன் உங்கள் களத்தை மாதிரியாகத் தொடங்கவும், பிழை இல்லாத மென்பொருளை உருவாக்குவதில் TypeScript கம்பைலர் உங்கள் அயராத கூட்டாளியாக இருக்கட்டும்.